package com.lanou3g.springbootsolr.service;

import com.lanou3g.springbootsolr.bean.Message;
import com.lanou3g.springbootsolr.dao.MessageDao;
import lombok.extern.slf4j.Slf4j;
import org.apache.solr.client.solrj.SolrClient;
import org.apache.solr.client.solrj.SolrQuery;
import org.apache.solr.client.solrj.SolrServerException;
import org.apache.solr.client.solrj.response.QueryResponse;
import org.apache.solr.common.SolrDocumentList;
import org.apache.solr.common.SolrInputDocument;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

@Slf4j
@Service
public class SolrService {

    @Autowired
    private SolrClient solrClient;

    @Autowired
    private MessageDao messageDao;

    public static final int BATCH_SIZE = 10;

    public static final String CORE_NAME = "lanou3g";

    /**
     * 将数据批量导入Solr中
     * @throws IOException
     * @throws SolrServerException
     */
    public void importData2Solr() throws IOException, SolrServerException {
        List<Message> messages = messageDao.loadAllMessage();
        List<SolrInputDocument> batchList = new ArrayList<>();
        messages.forEach((message -> {

            // 将message对象转换成solr的inputDocument
            SolrInputDocument inDoc = new SolrInputDocument();
            inDoc.addField("id", message.getId());
            inDoc.addField("from_id", message.getFromId());
            inDoc.addField("to_id", message.getToId());
            inDoc.addField("subject", message.getSubject());
            inDoc.addField("content", message.getContent());
            inDoc.addField("createtime", message.getCreatetime());
            inDoc.addField("status", message.getStatus());
            inDoc.addField("attachment", message.getAttachment());

            batchList.add(inDoc);
            if(batchList.size() % BATCH_SIZE == 0) {
                try {
                    solrClient.add(CORE_NAME ,batchList);
                    batchList.clear();
                    log.info("批量导入"+BATCH_SIZE+"条到solr.");
                } catch (SolrServerException e) {
                    e.printStackTrace();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }));

        if(batchList.size() > 0) {
            solrClient.add(CORE_NAME, batchList);
            log.info("批量导入"+batchList.size()+"条到solr.");
            batchList.clear();
        }
        log.info("数据导入完成！");

        // 提交数据到solr
//        solrClient.commit();  // 无参的需要在配置文件中将核心名称添加到solr url中，参见application.yml
        solrClient.commit(CORE_NAME);
    }


    /**
     * 从Solr中分页搜索数据
     * @param q 搜索关键字
     * @param fields 限制返回的结果集中只允许哪个字段
     * @param start 分页参数
     * @param pageSize   分页参数
     */
    public void searchFromSolr(String q, String[] fields, int start, int pageSize) {

        SolrQuery params = new SolrQuery(q);
        if(fields != null && fields.length > 0) {
            params.setFields(fields);
        }

        // 分页参数
        params.setStart(start);
        params.setRows(pageSize);

        // 不设置按照哪个字段搜索的时候，默认搜索哪个字段
        // （一般会将系统中所有支持检索的字段通过CopyField的方式拷贝到一个统一的字段上，用于搜索，比如下面的keywords）
        params.setParam("df", "keywords");

        // 设置搜索结果高亮显示
        params.setHighlight(true);
        // 设置往搜索结果中所有匹配关键字的地方添加指定的前缀和后缀（内容随意）
        params.setHighlightSimplePre("<i class=\"keywords\">");
        params.setHighlightSimplePost("</i>");

        try {
//            QueryResponse queryResp = solrClient.query(params);
            QueryResponse queryResp = solrClient.query(CORE_NAME, params);
            SolrDocumentList results = queryResp.getResults();
            long numFound = results.getNumFound();
            System.out.println("总共搜索到"+numFound+"条结果");
            results.forEach((solrDoc) -> {
                StringBuilder sb = new StringBuilder();
                sb.append("{");
                Collection<String> fieldNames = solrDoc.getFieldNames();
                fieldNames.forEach((fieldName) -> {
                    Object fieldValue = solrDoc.getFieldValue(fieldName);
                    sb.append("\""+fieldName+"\":\""+fieldValue+"\",");
                });
                if(sb.length() > 1) {
                    sb.deleteCharAt(sb.length() - 1);
                }
                sb.append("}");

                System.out.println("row: " + sb.toString());
            });
        } catch (SolrServerException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

    }
}
